package com.qifeng.modules.wechat;

import cn.binarywang.wx.miniapp.api.WxMaService;
import cn.binarywang.wx.miniapp.bean.WxMaJscode2SessionResult;
import cn.binarywang.wx.miniapp.bean.WxMaPhoneNumberInfo;
import cn.binarywang.wx.miniapp.bean.WxMaUserInfo;
import com.qifeng.common.base.RestResponse;
import com.qifeng.modules.userInfo.domain.UserInfo;
import com.qifeng.modules.userInfo.service.UserInfoService;
import com.qifeng.modules.wechat.config.WxConfiguration;
import io.swagger.annotations.ApiOperation;
import io.swagger.annotations.ApiParam;
import io.swagger.annotations.ApiResponse;
import io.swagger.annotations.ApiResponses;
import me.chanjar.weixin.common.error.WxErrorException;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.util.Date;

/**
 * 微信小程序用户接口
 */
@RestController
@RequestMapping("/wx/user/{appid}")
public class WxUserController {
    private final Logger logger = LoggerFactory.getLogger(this.getClass());

    @Autowired
    private UserInfoService userInfoService;

    /**
     * 登录接口
     *
     * @param appid
     * @param code
     * @return
     */
    @ApiOperation(value = "微信登录接口", notes = "")
    @ApiResponses({
            @ApiResponse(code = 200, message = "成功"),
            @ApiResponse(code = 404, message = "失败", response = RestResponse.class)
    })
    @GetMapping("/login")
    public RestResponse login(@PathVariable @ApiParam(value = "appid", required = true) String appid,
                              @RequestParam @ApiParam(value = "登录code", required = true) String code,
                              RestResponse response) {
        if (StringUtils.isBlank(code)) {
            return response.success("empty jscode");
        }
        final WxMaService wxService = WxConfiguration.getMaService(appid);
        try {
            WxMaJscode2SessionResult session = wxService.getUserService().getSessionInfo(code);
            this.logger.info(session.getSessionKey());
            this.logger.info(session.getOpenid());
            UserInfo info = userInfoService.findByOpenId(session.getOpenid());
            if (info == null) {
                UserInfo userInfo = new UserInfo();
                userInfo.setCreateTime(new Date());
                userInfo.setOpenId(session.getOpenid());
                userInfoService.create(userInfo);
                return response.success(userInfo);
            }
            return response.success(info);
        } catch (WxErrorException e) {
            e.printStackTrace();
            return response.success(e.toString());
        }
    }

    /**
     * <pre>
     * 获取用户信息接口
     * </pre>
     */
    @ApiOperation(value = "获取用户信息接口", notes = "")
    @ApiResponses({
            @ApiResponse(code = 200, message = "成功"),
            @ApiResponse(code = 404, message = "失败", response = RestResponse.class)
    })
    @GetMapping("/info")
    public RestResponse info(@PathVariable @ApiParam(value = "appid", required = true) String appid,
                             @ApiParam(value = "sessionKey", required = true) String sessionKey,
                             @ApiParam(value = "signature", required = true) String signature,
                             @ApiParam(value = "rawData", required = true) String rawData,
                             @ApiParam(value = "encryptedData", required = true) String encryptedData,
                             @ApiParam(value = "iv", required = true) String iv,
                             RestResponse response) {
        final WxMaService wxService = WxConfiguration.getMaService(appid);

        // 用户信息校验
        if (!wxService.getUserService().checkUserInfo(sessionKey, rawData, signature)) {
            return response.success("user check failed");
        }

        // 解密用户信息
        WxMaUserInfo userInfo = wxService.getUserService().getUserInfo(sessionKey, encryptedData, iv);

        return response.success(userInfo);
    }

    /**
     * <pre>
     * 获取用户绑定手机号信息
     * </pre>
     */
    @ApiOperation(value = "获取用户绑定手机号信息", notes = "")
    @ApiResponses({
            @ApiResponse(code = 200, message = "成功"),
            @ApiResponse(code = 404, message = "失败", response = RestResponse.class)
    })
    @GetMapping("/phone")
    public RestResponse phone(@PathVariable @ApiParam(value = "appid", required = true) String appid,
                              @ApiParam(value = "sessionKey", required = true) String sessionKey,
                              @ApiParam(value = "signature", required = true) String signature,
                              @ApiParam(value = "rawData", required = true) String rawData,
                              @ApiParam(value = "encryptedData", required = true) String encryptedData,
                              @ApiParam(value = "iv", required = true) String iv,
                              RestResponse response) {
        final WxMaService wxService = WxConfiguration.getMaService(appid);

        // 用户信息校验
        if (!wxService.getUserService().checkUserInfo(sessionKey, rawData, signature)) {
            return response.success("user check failed");
        }

        // 解密
        WxMaPhoneNumberInfo phoneNoInfo = wxService.getUserService().getPhoneNoInfo(sessionKey, encryptedData, iv);

        return response.success(phoneNoInfo);
    }

}
